package com.autumn.scheduler.domain.services.impl;

import org.quartz.JobKey;
import org.quartz.Scheduler;
import org.quartz.SchedulerException;
import org.quartz.TriggerKey;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;

import com.autumn.mybatis.criterion.LockModeEnum;
import com.autumn.scheduler.domain.entities.AutumnJobDetails;
import com.autumn.scheduler.domain.repositories.IAutumnJobDetailsQueryRepository;
import com.autumn.scheduler.domain.repositories.IAutumnJobDetailsRepository;
import com.autumn.scheduler.domain.repositories.IAutumnJobLogRepository;
import com.autumn.scheduler.job.JobConstants;
import com.autumn.util.ExceptionUtils;
import com.autumn.util.function.FunctionOneAction;

/**
 * 服务抽象
 * 
 * @author 老码农
 *
 *         2018-07-05 16:43:29
 */
public abstract class AbstractAutumnSchedulerService {

	@Autowired
	@Qualifier(JobConstants.AUTUMN_QUARTZ_SCHEDULER)
	protected Scheduler scheduler;

	@Autowired
	protected IAutumnJobDetailsRepository jobDetailsRepository;
	@Autowired
	protected IAutumnJobDetailsQueryRepository jobQueryDetailsRepository;
	@Autowired
	protected IAutumnJobLogRepository logRepository;

	/**
	 * 获取调度器名称
	 * 
	 * @return
	 */
	protected String getSchedulerName() {
		try {
			return scheduler.getSchedulerName();
		} catch (SchedulerException e) {
			return JobConstants.AUTUMN_QUARTZ_SCHEDULER;
		}
	}

	/**
	 * 删除任务
	 * 
	 * @param key
	 * @param delAction
	 * @param threadSleep
	 *
	 */
	protected void deleteJob(JobKey key, FunctionOneAction<JobKey> delAction, Integer threadSleep) {
		TriggerKey triggerKey = TriggerKey.triggerKey(key.getName(), key.getGroup());
		try {
			scheduler.pauseTrigger(triggerKey);
			scheduler.unscheduleJob(triggerKey);
			if (threadSleep != null && threadSleep.intValue() > 0) {
				try {
					// 任务可能正在运行，所以需要阻塞
					Thread.sleep(threadSleep.intValue());
				} catch (InterruptedException e) {
				}
			}
			scheduler.deleteJob(key);
			delAction.apply(key);
		} catch (SchedulerException e) {
			throw ExceptionUtils.throwApplicationException(e.getMessage(), e);
		}
	}

	/**
	 * 
	 * @param id
	 * @return
	 */
	protected JobKey getJobKey(long id) {
		AutumnJobDetails details = jobDetailsRepository.getByLock(id, LockModeEnum.UPDATE);
		if (details == null) {
			return null;
		}
		return getJobKey(details);
	}

	/**
	 * 
	 * @param details
	 * @return
	 *
	 */
	protected JobKey getJobKey(AutumnJobDetails details) {
		return JobKey.jobKey(details.getJobName(), details.getJobGroup());
	}
}
